#pragma once

#include "Vector2.h"
#include <cmath>

namespace lib3dw
{
	struct Vector3 
	{
		float x, y, z;

		Vector3()
		{
			x = y = z = 0.0;
		}

		Vector3(const float ixyz)
		{
			x = y = z = ixyz;
		}

		Vector3(const float ix, const float iy, const float iz)
		{
			x = ix;
			y = iy;
			z = iz;
		}

		Vector3(const Vector2 iv, const float iz)
		{
			x = iv.x;
			y = iv.y;
			z = iz;
		}
		
		Vector3(const float ix, const Vector2 iv)
		{
			x = ix;
			y = iv.x;
			z = iv.y;
		}

		operator float *() const
		{
			return (float *) &x; 
		}

		void operator += (const float s);
		void operator += (const Vector3 &v);
		void operator -= (const float s);
		void operator -= (const Vector3 &v);
		void operator *= (const float s);
		void operator *= (const Vector3 &v);
		void operator /= (const float s);
		void operator /= (const Vector3 &v);
		Vector3& cross(const Vector3& v);
		float length() const;
		Vector3& flip();
		Vector3& normalize();
		float dot(Vector3 &u);
		
		Vector2 xy() const
		{
			return Vector2(x, y);
		}
		
		Vector2 yz() const
		{
			return Vector2(y, z);
		}
		
		Vector2 xz() const
		{
			return Vector2(x, z);
		}

		
	};

	Vector3 operator + (const Vector3 &u, const Vector3 &v);
	Vector3 operator + (const Vector3 &v, const float s);
	Vector3 operator + (const float s, const Vector3 &v);

	Vector3 operator - (const Vector3 &u, const Vector3 &v);
	Vector3 operator - (const Vector3 &v, const float s);
	Vector3 operator - (const float s, const Vector3 &v);
	Vector3 operator - (const Vector3 &v);

	Vector3 operator * (const Vector3 &u, const Vector3 &v);
	Vector3 operator * (const float s, const Vector3 &v);
	Vector3 operator * (const Vector3 &v, const float s);

	Vector3 operator / (const Vector3 &u, const Vector3 &v);
	Vector3 operator / (const Vector3 &v, const float s);
	Vector3 operator / (const float s, const Vector3 &v);

	bool operator == (const Vector3 &u, const Vector3 &v);
	
	float dot(const Vector3 &u, const Vector3 &v);
	Vector3 cross(const Vector3 &u, const Vector3& v);
}